﻿using Google.Protobuf.WellKnownTypes;
using Grpc.Net.Client;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using SHKF.B2C.BaseHosted;
using SHKF.B2C.BLL;
using SHKF.B2C.BLL.Center;
using SHKF.B2C.BLL.LM;
using SHKF.B2C.BLL.SugarIOC;
using SHKF.B2C.BLL.WorkingCenter;
using SHKF.B2C.Hosted;
using SHKF.B2C.Model; 
using SHKF.B2C.Model.Entity.Center;
using SHKF.B2C.Model.Entity.Sale;
using SHKF.B2C.Model.Entity.WorkingCenter;
using SHKF.B2C.SaleServices.Protos;
using SHKF.B2C.YouZanYun.BLL;
using SHKF.B2C.YouZanYun.Model.Dto.Order;
using SHKF.B2C.YouZanYun.Model.Dto.Order.Msg;
using SHKF.B2C.YouZanYun.Model.Dto.Order.Msg.info;
using SHKF.B2C.YouZanYun.Model.Dto.Secret;
using SHKF.B2C.YouZanYun.Model.Dto.Token;
using SHKF.B2C.YouZanYun.Model.Entity.Order;
using SHKF.B2C.YouZanYun.Model.Inter.UpdateBranch;
using SqlSugar;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Web;
using static SHKF.B2C.SaleServices.Protos.GSaleService;

namespace SHKF.B2C.YouZanYun.Service.Controllers
{
    [Route("[controller]")]
    [ApiController]
    public class CallBackController : BaseController
    {
        
        private readonly HttpClientYouZanYunS httpClient;
        private readonly ShopMapBLL shopMapBLL;
        private readonly ProductInfoBLL productInfoBLL;
        private readonly ProductInfoMapBLL productInfoMapBLL;
        private readonly SaleContentBLL saleContentBLL; 
        private readonly YZYOrderBLL orderBll;
        private readonly WorkingCenterBLL workingCenterBLL;
        private readonly WareHouseDataWarehousBLL wareHouseDataWarehousBLL;
        private readonly WareHouseDataAllBLL wareHouseDataAll;
        private readonly IConfiguration configuration;

        public CallBackController(ILogger<CallBackController> logger,
            HttpClientYouZanYunS httpClient,
            ShopMapBLL shopMapBLL,
            ProductInfoBLL productInfoBLL,
            ProductInfoMapBLL productInfoMapBLL,
            SaleContentBLL saleContentBLL, 
            YZYOrderBLL orderBll,
            WorkingCenterBLL workingCenterBLL,
            WareHouseDataWarehousBLL wareHouseDataWarehousBLL,
            WareHouseDataAllBLL wareHouseDataAll,
            IConfiguration Configuration) : base(logger)
        {
            SaleRequest request = new SaleRequest();


            try
            { 
                request.SaleDate = Google.Protobuf.WellKnownTypes.Timestamp.FromDateTime(DateTime.Now.ToUniversalTime());
            }
            catch (Exception ex)
            { 
                throw ex;
            }
          


            this.httpClient = httpClient;
            this.shopMapBLL = shopMapBLL;
            this.productInfoBLL = productInfoBLL;
            this.productInfoMapBLL = productInfoMapBLL;
            this.saleContentBLL = saleContentBLL; 
            this.orderBll = orderBll;
            this.workingCenterBLL = workingCenterBLL;
            this.wareHouseDataWarehousBLL = wareHouseDataWarehousBLL;
            this.wareHouseDataAll = wareHouseDataAll;
            configuration = Configuration;
        }

        public async Task<IActionResult> Post()
        { 
            IHeaderDictionary headers = base.HttpContext.Request.Headers;
            string strEventType = ""; //消息的业务标识，用于区分消息事件类型。英文表示的消息，具体详见各个消息事件的业务标识
            string strEventSign = ""; //防伪签名 ：MD5 (client_id+entity+client_secret); 其中 entity 是从 RequestBody 读取的内容

            if (headers.ContainsKey("Event-Type"))
            {
                strEventType = headers["Event-Type"];

                this.logger.LogInformation("Event-Type:" + strEventType);
            }

            if (headers.ContainsKey("Event-Sign"))
            {
                strEventSign = headers["Event-Sign"];

                this.logger.LogInformation("Event-Sign:" + strEventSign);
            }

            var request = this.Request;
            string json = "";
            if (request.Method.ToLower().Equals("post"))
            {
                request.Body.Seek(0, SeekOrigin.Begin);
                var reader = new StreamReader(request.Body, Encoding.UTF8);
                json = reader.ReadToEnd();
                request.Body.Seek(0, SeekOrigin.Begin);
            }

            SuccessDto success = new SuccessDto(); 
            switch (strEventType)
            {
                //case "trade_TradeCreate":  
                //case "trade_TradePaid": //交易支付 
                case "trade_TradeBuyerPay": //买家付款(即商家待发货)
                    await this.trade_TradeBuyerPay(json);

                    //更新有赞云

                    break;
                default:
                    this.logger.LogInformation("null Event-Type");
                    break;
            }

            return new JsonResult(success);
        }

        private async Task<string> trade_TradeBuyerPay(string json)
        {
            if (!string.IsNullOrEmpty(json))
            {
                this.logger.LogInformation("json:" + json);
 
                OrderDto order = JsonConvert.DeserializeObject<OrderDto>(json);
                string msg = HttpUtility.UrlDecode(order.msg, Encoding.UTF8);
                OrderMsg orderMsg = JsonConvert.DeserializeObject<OrderMsg>(msg);

                //获取Token 
                this.httpClient.authority_id = order.kdt_id.ToString();
                TokenYZYDto token = await this.httpClient.GetToken();

                if (token != null)
                {
                    if (!string.IsNullOrEmpty(token.message))
                    {
                        base.WriteInformation("CallBack", $"authority_id:{this.httpClient.authority_id }:{token.message} code:{token.code}");
                        return token.message;
                    }

                    //解密收货人信息
                    List<string> sources = new List<string>();
                    Address_Info address_info = orderMsg.full_order_info.address_info;

                    string receiver_tel = address_info.receiver_tel;
                    string delivery_address = address_info.delivery_address;
                    string receiver_name = address_info.receiver_name;
                    string buyer_phone = orderMsg.full_order_info.buyer_info.buyer_phone;

                    sources.Add(receiver_tel);
                    sources.Add(delivery_address);
                    sources.Add(receiver_name);
                    sources.Add(buyer_phone);

                    DecryptsDto decrypts = await this.httpClient.DecryptBatch(sources);
                    if (decrypts.code != 200)
                    {
                        base.WriteInformation("CallBack->DecryptBatch", $"code:{decrypts.code} message:{decrypts.message}");
                    }
                    else
                    {
                        receiver_tel = decrypts.data[address_info.receiver_tel].ToString();
                        delivery_address = decrypts.data[address_info.delivery_address].ToString();
                        receiver_name = decrypts.data[address_info.receiver_name].ToString();
                        buyer_phone = decrypts.data[orderMsg.full_order_info.buyer_info.buyer_phone].ToString();
                    }

                    address_info.receiver_tel = receiver_tel;
                    address_info.delivery_address = delivery_address;
                    address_info.receiver_name = receiver_name;
                    
                    TradeContentEntity orderContent = new TradeContentEntity();
                    orderContent.buyer_phone = buyer_phone;
                   
                    //主体信息  
                    CreateOrder(orderContent, order, orderMsg.full_order_info);

                    //订单收货地址信息结构
                    CreateOrderDelivery(orderContent, address_info);

                    //订单买家信息结构体
                    CreateOrderBuyer(orderContent, orderMsg.full_order_info.buyer_info);

                    //支付信息
                    CreateOrderPlay(orderContent, orderMsg.full_order_info.pay_info);

                    CreateOrderPromotion(orderContent, orderMsg.order_promotion);

                    //备注
                    CreateOrderRemark(orderContent, orderMsg.full_order_info.remark_info);

                    //优惠暂时没有

                    //明细
                    List<TradeDetailEntity> orderDetails = new List<TradeDetailEntity>();
                    List<Orders> details = orderMsg.full_order_info.orders;
                    if (details != null)
                    {
                        foreach (Orders detail in orderMsg.full_order_info.orders)
                        {
                            orderDetails.Add(detail);
                        }
                    }

                    //保存有赞云的数据
                    int result = this.orderBll.SaveAll(orderContent, orderDetails); 
                    if (result >= 0)
                    {
                        if( result != 2)
                        {
                            base.WriteInformation("trade_TradeBuyerPay", $"1.保存有赞云单据{orderContent.id}成功!");
                        }

                        //保存解析后的销售单到PtE_LM
                        CreateTSaleContent(orderContent, orderDetails); 
                    } 

                }
                else
                {
                    base.WriteInformation("trade_TradeBuyerPay", order.kdt_id + "token为空");
                }
            }

            return "";
        }

        private void CreateOrder(TradeContentEntity orderContent, OrderDto order, Full_Order_Info full_order_info)
        {
            orderContent.id = order.id;
            orderContent.kdt_id = order.kdt_id;
            orderContent.kdt_name = order.kdt_name;
            orderContent.msg_id = order.msg_id;
            orderContent.root_kdt_id = order.root_kdt_id;
            orderContent.sendCount = order.sendCount;
            orderContent.status = order.status;

            orderContent.created = full_order_info.order_info.created; ;
            orderContent.update_time = full_order_info.order_info.update_time;
            orderContent.pay_time = full_order_info.order_info.pay_time;
            orderContent.pay_type = full_order_info.order_info.pay_type;
            orderContent.refund_state = full_order_info.order_info.refund_state;
        }

        private void CreateOrderDelivery(TradeContentEntity orderContent, Address_Info address_info)
        {
            //经纬度
            address_extra address_Extra = JsonConvert.DeserializeObject<address_extra>(address_info.address_extra);

            orderContent.longitude = address_Extra.lon;
            orderContent.latitude = address_Extra.lat;
            orderContent.areaCode = address_Extra.areaCode;
            orderContent.delivery_address = address_info.delivery_address;
            orderContent.delivery_city = address_info.delivery_city;
            orderContent.delivery_district = address_info.delivery_district;
            orderContent.delivery_end_time = address_info.delivery_end_time;
            orderContent.delivery_postal_code = address_info.delivery_postal_code;
            orderContent.delivery_province = address_info.delivery_province;
            orderContent.delivery_start_time = address_info.delivery_start_time;
            orderContent.receiver_name = address_info.receiver_name;
            orderContent.receiver_tel = address_info.receiver_tel;
        }

        private void CreateOrderBuyer(TradeContentEntity orderContent, Buyer_Info buyer_info)
        {
            orderContent.yz_open_id = buyer_info.yz_open_id; 
            orderContent.outer_user_id = buyer_info.outer_user_id;
        }

        private void CreateOrderPlay(TradeContentEntity orderContent, Pay_Info pay)
        {
            orderContent.total_fee = pay.total_fee;
            orderContent.payment = pay.payment;
            orderContent.post_fee = pay.post_fee;
        }

        private void CreateOrderPromotion(TradeContentEntity orderContent, Order_Promotion promotion)
        {
            if (promotion != null)
            {
                orderContent.discount_fee = promotion.item_discount_fee + promotion.order_discount_fee;
            }

        }

        private void CreateOrderRemark(TradeContentEntity orderContent, Remark_Info remark)
        {
            orderContent.buyer_message = remark.buyer_message;
            orderContent.star = remark.star;
            orderContent.trade_memo = remark.trade_memo;
        }

        //存储解析后的销售单
        private void CreateTSaleContent(TradeContentEntity content, List<TradeDetailEntity> details)
        {
            try
            {
                //B2C平台的映射关系
                ShopMapEntity shopMapEntity = this.shopMapBLL.GetShop(content.kdt_id, PlatformEnum.YouZanYun);
                if (shopMapEntity == null)
                {
                    base.WriteInformation("CreateTSaleContent", $"有赞云门店ID:{content.kdt_id}在B2C平台中没有映射");
                    return;
                }

                SaleContentEntity saleContent = new SaleContentEntity();

                int CompanySN = shopMapEntity.CompanySN;
                int ShopSN = shopMapEntity.ShopSN;

                saleContent.ID = content.id;
                saleContent.SN = content.SN;
                saleContent.ShopSN = ShopSN;
                saleContent.SaleDate = content.created;
                saleContent.pDate = DateTime.Now;

                //购买者
                saleContent.CompanySN = CompanySN;
                saleContent.CustName = "";
                saleContent.CustTel = content.buyer_phone;
                saleContent.CustAddress = "";

                //收获人
                saleContent.DeliveryName = content.receiver_name;
                saleContent.DeliveryTel = content.receiver_tel;
                saleContent.DeliveryAddress = content.delivery_province + content.delivery_city + content.delivery_district + content.delivery_address;
                saleContent.Longitude = content.longitude;
                saleContent.Latitude = content.latitude;

                //支付
                saleContent.Total = content.total_fee;
                saleContent.FavorTotal = content.discount_fee;
                saleContent.Payment = content.payment;

                saleContent.Platform = PlatformEnum.YouZanYun;
                saleContent.PlatformID = content.id;

                //明细
                List<SaleDetailEntity> detialList = new List<SaleDetailEntity>();

                foreach (TradeDetailEntity orderDetail in details)
                {
                    //由于有赞云总店同一产品的item_id和分店的item_id不一致
                    string no = orderDetail.item_no;
                    if (no == "")
                    {
                        no = orderDetail.item_barcode;
                    }

                    //以后改成Upc
                    //long ProductVSN = this.productInfoMapBLL.GetProductSN(no, PlatformEnum.YouZanYun);
                    //if (ProductVSN > 0)
                    //{
                    //    SaleDetailEntity detail = new SaleDetailEntity();
                    //    detail.SN = orderDetail.SN;
                    //    detail.FKSN = orderDetail.FKSN;
                    //    detail.Qty = orderDetail.num;
                    //    detail.Price = orderDetail.price;
                    //    detail.Total = orderDetail.payment;

                    //    detail.ProductSN = ProductVSN;
                    //    detail.ItemId = orderDetail.item_id;
                    //    detialList.Add(detail);
                    //}
                    //else
                    //{
                    //    base.WriteInformation("CallBack", $"有赞云单号:{content.id}中item_id:{orderDetail.item_id}没有在B2C平台中映射");
                    //} 
                }

                //long SN = this.saleContentBLL.Save(saleConent, detialList);
                //saleConent.SN = SN;

                //调用grpc创建erp销售单 
                this.SendErpSale(saleContent, detialList);

            }
            catch (Exception ex)
            {
                base.WriteException("CreateTSaleContent", ex);
            }
  
        }

        private void SendErpSale(SaleContentEntity  saleContent,  List<SaleDetailEntity> details)
        {
            try
            {
                AppContext.SetSwitch("System.Net.Http.SocketsHttpHandler.Http2UnencryptedSupport", true);
                string address = this.configuration.GetSection("grpc").Value;
                base.WriteInformation("SendErpSale",$"order:{saleContent.ID} address:{address}" );

                GrpcChannel channel = GrpcChannel.ForAddress(address);

                SaleRequest request = new SaleRequest();

                request.ID = saleContent.ID;
                request.ShopSN = saleContent.ShopSN;        //虚拟店铺SN
                request.CompanySN = saleContent.CompanySN;
                 
                request.SaleDate = Google.Protobuf.WellKnownTypes.Timestamp.FromDateTime(DateTime.Now.ToUniversalTime()); ;

                request.CustAddress = "";
                request.CustName = "";
                request.CustTel = saleContent.CustTel;

                //收获人
                request.DeliveryName = saleContent.DeliveryName;
                request.DeliveryTel = saleContent.DeliveryTel;
                request.DeliveryAddress = saleContent.DeliveryAddress;
                request.Longitude = saleContent.Longitude;
                request.Latitude = saleContent.Latitude;

                //支付
                request.Total = (float)saleContent.Total;
                request.FavorTotal = (float)saleContent.FavorTotal;
                request.Payment = (float)saleContent.Payment;

                request.Platform = PlatformEnum.YouZanYun;
                request.PlatformID = saleContent.PlatformID;

                request.SN = saleContent.SN;

                foreach (SaleDetailEntity detail in details)
                {
                    SaleDetail rpcDetail = new SaleDetail();
                    rpcDetail.SN = detail.SN;
                    rpcDetail.FKSN = saleContent.SN;
                    rpcDetail.ProductSN = detail.ProductSN;
                    rpcDetail.Qty = detail.Qty;
                    rpcDetail.Price = (float)detail.Price;
                    rpcDetail.Total = (float)detail.Total;
                    rpcDetail.ItemId = detail.ItemId;

                    request.Detail.Add(rpcDetail);
                }

                base.WriteInformation("SendErpSale", $"2.有赞云单据:{saleContent.PlatformID}调用grpc");
                new GSaleServiceClient(channel).Save(request);
            }
            catch (Exception ex)
            { 
                throw ex;
            } 
        }




        #region 更新有赞云

        //private void UpdateYZYQty(TradeContentEntity content, List<TradeDetailEntity> details)
        //{

        //}

        //private void Update(string warehousSN, long ProductSN)
        //{
        //    //--------------------1.获取有赞云分店SN
        //    ShopRelatedEntity shopRelatedEntity = this.workingCenterBLL.QueryShopRelate(warehousSN);
        //    if (shopRelatedEntity == null || shopRelatedEntity.ShopVSN == 0)
        //    {
        //        this.logger.LogError($"ProductSN:{ProductSN} >> 门店:{warehousSN}在Erp中没有映射!");
        //        return;
        //    }

        //    int ShopVSN = shopRelatedEntity.ShopVSN;            //虚拟分店SN 
        //    ShopMapEntity shopMap = this.shopMapBLL.Get(ShopVSN, PlatformEnum.YouZanYun);
        //    if (shopMap == null || shopMap.app_poi_code == 0)
        //    {
        //        this.logger.LogError($"ProductSN:{ProductSN} 门店:{ShopVSN}在B2C中没有映射!");
        //        return;
        //    }

        //    long node_kdt_id = shopMap.app_poi_code; //有赞分店SN

        //    //--------------------2.获取有赞云产品SN
        //    ProductInfoRelatedEntity productRelate = this.workingCenterBLL.QueryProductInfoRelated(warehousSN, ProductSN);
        //    if (productRelate == null || productRelate.ProductVSN == 0)
        //    {
        //        this.logger.LogError($"ProductSN:{ProductSN} 在B2C中没有映射!");
        //        return;
        //    }
        //    long productVSV = productRelate.ProductVSN;

        //    //V_ProductInfoMap productMap = this.productInfoBLL.QueryVProductInfoMap(productVSV, PlatformEnum.YouZanYun); 
        //    ProductInfoMapEntity productMap = this.productInfoBLL.QueryMap(productVSV, PlatformEnum.YouZanYun);
        //    if (productMap == null || productMap.app_medicine_id == 0)
        //    {
        //        this.logger.LogError($"ProductSN:{ProductSN}  虚拟产品SN:{productVSV} 没有配置有赞云平台产品SN!");
        //        return;
        //    }

        //    int Qty = GetTotalQty(shopRelatedEntity.ShopVSN, productRelate.ProductVSN, ProductSN);  //库存总量

        //    UpdateQtyYzy(node_kdt_id, productMap.app_medicine_id, ProductSN, Qty, shopMap.CompanySN);
        //}

        //private int GetTotalQty(int ShopVSN, long ProductVSN, long erpProductSN)
        //{
        //    List<ShopRelatedEntity> shopList = this.workingCenterBLL.QueryShopRelateList(ShopVSN);                           //分店Erp映射
        //    List<ProductInfoRelatedEntity> productList = this.workingCenterBLL.QueryProductInfoRelatedList(ProductVSN);      //产品Erp映射
        //    int Qty = 0;
        //    if (shopList != null && productInfoBLL != null)
        //    {
        //        foreach (ShopRelatedEntity shopRelate in shopList) //分店
        //        {
        //            //统计erp库存 
        //            ProductInfoRelatedEntity product = productList.Where<ProductInfoRelatedEntity>(ww => ww.WarehousSN == shopRelate.WarehousSN)
        //                                                        .FirstOrDefault(); //erp产品SN

        //            if (product != null && product.ProductSN > 0)
        //            {
        //                try
        //                {
        //                    SqlSugarClient erpClient = DbScoped.CreateSugar(shopRelate.ServerName); //erp操作实例  
        //                    erpClient.ChangeDatabase("YZ_Med_LMSystem");

        //                    //Erp的库存数
        //                    string sql = "select sum(qty) as qty from WM_WareHouseData where qty > 0 and productSN = " + product.ProductSN.ToString();

        //                    int tempQty = (int)erpClient.Ado.GetDecimal(sql);
        //                    Qty += tempQty;

        //                    //更新分店库存
        //                    WareHouseDataWarehousEntity info = new WareHouseDataWarehousEntity();
        //                    info.ShopVSN = ShopVSN;
        //                    info.WarehousSN = shopRelate.WarehousSN;
        //                    info.ProductVSN = ProductVSN;
        //                    info.Qty = tempQty;
        //                    this.wareHouseDataWarehousBLL.Save(info);
        //                }
        //                catch (Exception ex)
        //                {
        //                    throw ex;
        //                }
        //            }
        //        }

        //        //更新总库存
        //        WareHouseDataAllEntity infoAll = new WareHouseDataAllEntity();
        //        infoAll.ShopVSN = ShopVSN;
        //        infoAll.ProductVSN = ProductVSN;
        //        infoAll.Qty = Qty;
        //        this.wareHouseDataAll.Save(infoAll);
        //    }
        //    else
        //    {
        //        this.logger.LogInformation($"Product:{erpProductSN} erp分店映射没配置,或者erp产品映射没配置");
        //    }


        //    //更新总店库存

        //    return Qty;
        //}

        //private async void UpdateQtyYzy(long node_kdt_id, long app_medicine_id, long ProductSN, int Qty, long CompanySN)
        //{
        //    ItemUpdateRequest data = new ItemUpdateRequest();

        //    data.root_item_id = app_medicine_id;    //商品
        //    List<ItemUpdateParam> list = new List<ItemUpdateParam>();
        //    ItemUpdateParam itemUpdateParam = new ItemUpdateParam();
        //    itemUpdateParam.stock_num = Qty;
        //    //itemUpdateParam.price = (long)price * 100;
        //    itemUpdateParam.node_kdt_id = node_kdt_id;  //有赞分店SN
        //    list.Add(itemUpdateParam);
        //    data.no_sku_update_open_param_list = list;

        //    //获取有赞总部SN
        //    long app_poi_code2 = this.shopMapBLL.GetKdtId(CompanySN);
        //    this.httpClient.authority_id = app_poi_code2.ToString();
        //    try
        //    {
        //        ItemUpdateResult result = await this.httpClient.BranchUpdateStock(data);
        //        if (result.success)
        //        {
        //            foreach (ItemUpdateData data1 in result.data)
        //            {
        //                if (!data1.is_success)
        //                {
        //                    this.logger.LogInformation($"{ProductSN}:{data1.message}");
        //                }
        //            }

        //            this.logger.LogInformation($"ProductSN:{ProductSN}: 更新成功！");
        //        }
        //        else
        //        {
        //            this.logger.LogError($"ProductSN:{ ProductSN}:{result.message}-{result.request_id}");
        //        }
        //    }
        //    catch (Exception ex)
        //    {
        //        this.logger.LogError($"ProductSN:{ ProductSN}:{ex.Message}");
        //    }
        //}

        #endregion

    }
}
